<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en">
<head>
	<title>Adv. Example: Setting and Using Styles</title>
	<link type="text/css" rel="stylesheet" href="css/examples.css" />
	<link type="text/css" rel="stylesheet" href="../os3grid.css" />
	<script src="../os3grid.js" type="text/javascript"></script>
	<script src="../form_validators.js" type="text/javascript"></script>
</head>
<body>
<div id="block_top">
	<h2 class="center">OS3Grid Advanced Example: Using OS3Grid to Edit a Dataset</h2>
	<h4 class="center">By Fabio Rotondo - fsoft (@) sourceforge ( dot ) net</h4>
</div>

<div id="block_left">
	<div class="menu_title">Examples</div>

	<div>
		<a href="index.html">Main Page</a><br />
		<a href="ex1.html">Simple Grid</a><br />
		<a href="ex2.html">Sortable Grid</a><br />
		<a href="ex3.html">Sortable Grid</a><br />
		<a href="ex4.html">Editable Grid</a><br />
		<a href="ex5.html">Custom Callbacks</a><br />
		<a href="ex6.html">Rows Selection</a><br />
		<a href="ex7.html">Column Resize</a><br />
		<a href="ex8.html">Column Renderers</a><br />
	</div>

	<div class="menu_title">Advanced Examples</div>
	<div>
		<a href="adv_styles.html">Setting and Using Styles</a><br />
		<a href="adv_edit.html">Using OS3Grid to edit a dataset</a><br />
		<a href="adv_cell_manip.html">Advanced Cell Value Manipulation</a><br />
	</div>

	<div class="menu_title">Support OS3Grid</div>
	<a href="http://sourceforge.net/donate/index.php?group_id=132180" target="_blank"><img src="http://images.sourceforge.net/images/project-support.jpg" width="88" height="32" border="0" alt="Support OS3Grid" /> </a>
</div>

<div id="block_middle">
	<div>
		<p>
		One of the most common questions about OS3Grid is <i>can I edit a dataset and then save all changes?</i> <br />
		The answer is: <strong>it depends</strong>. You actually need some good Javascript knowledge to do that.
		Don't forget that OS3Grid is just a <strong>presentation layer</strong> and it is as much generic as possible,
		so it does not offers <i>commodities</i> to do special tasks. <br />
		</p>

		<p>
		OS3Grid 0.6 introduces some new cool features that helps you track a row by adding the new methods
		<tt>set_row_attr()</tt> and <tt>get_row_attrs()</tt>.<br />
		By using these methods, you can, for example, define an <i>unique id</i> to each row that will remain
		untouched even if the user changes all row data and sorts the OS3Grid as many times she wants to.
		</p>
	
		<p>
		In our example, we'll have a dataset of user details (nick, name, e-mail addr).  Binded to each row, we'll create
		a special <i>'magic'</i> attribute that will be the row <i>unique id</i>. For this example, the 'magic' value will
		be just the user's nick prepended by the word <i>magic</i>. <br />

		In this example, we'll define the dataset by using the standard <tt>add_row()</tt> method and then by calling the
		new <tt>set_row_attrs()</tt> method with <tt>-1</tt> as the first parameter which means <i>"the last column just added</i>, 
		just like in all the other OS3Grid methods that need a row number. By calling this method we set the <tt>'magic'</tt> value
		that'll help us identify the row uniquely in the dataset. <br />
		As a further optimization, our code will send back just the rows the user will actually modify and not all the dataset, so 
		we can optimize bandwith. To do so, we'll add another attribute, called <tt>'changed'</tt> set by default to <tt>'NO'</tt>.
		We'll do stuff like the following code excerpt:

		<div class="code"><pre>
				g.add_row ( "fsoft", "Fabio Rotondo", "fsoft (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-fsoft' );
				g.set_row_attr ( -1, 'changed', 'NO' );
		</pre></div>
		</p>

		<p>
		To be able to set the row <tt>'change'</tt> attribute to <tt>'YES'</tt>, we'll need to define a <strong>callback</strong>
		to change the value after the user has actually changed the row values. Our callback function will be the following:

		<div class="code"><pre>
				function row_modified ( grid, cell_pos, row_num, new_val )
				{
					var attrs = grid.get_row_attrs ( row_num );
					attrs [ 'changed' ] = 'YES';
				}	
		</pre></div>

		and, later, after OS3Grid instantiation, we'll bind the callback, with the following code:
		<div class="code"><pre> g.onchange = row_modified; </pre></div>

		</p>

		<p>
		To gather the results, this example shows two functions:
			<ul>
			<li><tt>collect_data()</tt> shows you how to cycle through OS3Grid dataset and shows values by using the classic <tt>alert()</tt> method.</li>
			<li><tt>post_form()</tt> will collect all OS3Grid data and send them to an imaginary site: remember to define the <tt>your.url.here</tt> value
			    inside the example function  to see it working for real.
			</li>
			</ul>

		Please, note that all functions will reset the <tt>'changed'</tt> attribute to <tt>'NO'</tt>, once called so that the changed rows are notified only once.
		</p>

		<div class="result">
			<div id="my_form"></div>
			<div id="grid"></div>
			<script type="text/javascript">
				// This function is an example showing you how to collect back data from an OS3Grid
				// The ``g`` param is the OS3Grid object instance we want the data back
				function collect_data ( g )
				{
					var l = g.length ();
					var t;
					var data, attrs;

					for ( t = 0; t < l; t ++ )
					{
						data = g.get_row ( t );
						attrs = g.get_row_attrs ( t );

						if ( attrs [ 'changed' ] == 'NO' ) continue;
						attrs [ 'changed' ] = 'NO';

						alert ( "Changed: " + data [ 0 ] + " - " + attrs [ 'magic' ] );
					}

					alert ( "Collection DONE!" );
				}

				function post_form ( g, form_id )
				{
					var frm = document.getElementById ( form_id );
					if ( ! frm ) alert ( form_id + " not found!" );

					var l = g.length ();
					var t;
					var data, attrs;
					var s = "";
					var i, v;

					s = '<form id="' + form_id + '" method="POST" action="http://your.url.here" target="_blank">';

					for ( t = 0; t < l; t ++ )
					{
						data = g.get_row ( t );
						attrs = g.get_row_attrs ( t );

						if ( attrs [ 'changed' ] == 'NO' ) continue;

						attrs [ 'changed' ] = 'NO';

						for ( i = 0; i < data.length; i ++ )
							s += '<input type=\"hidden\" name=\"' + attrs [ 'magic' ] + '_' + i + '" value="' + data [ i ] + '" />';
					}

					s += '</form>';

					frm.innerHTML = s;

					document.getElementById ( form_id ).submit ();
				}

				function row_modified ( grid, cell_pos, row_num, new_val )
				{
					var attrs = grid.get_row_attrs ( row_num );
					attrs [ 'changed' ] = 'YES';
				}	


				// Create an OS3Grid instance
				var g = new OS3Grid ( 'grid' );

				// Set the callback for modifications
				g.onchange = row_modified;

				// g.set_size ( "400", "200" );
				
				// Grid Headers are the grid column names
				g.set_headers ( 'nick', 'name', 'email addr' );

				// Now, we add some rows
				g.add_row ( "fsoft", "Fabio Rotondo", "fsoft (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-fsoft' );
				g.set_row_attr ( -1, 'changed', 'NO' );

				g.add_row ( "nick", "Nick Fury", "nick (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-nick' );
				g.set_row_attr ( -1, 'changed', 'NO' );

				g.add_row ( "john", "John JJ Jameson", "john (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-john' );
				g.set_row_attr ( -1, 'changed', 'NO' );

				g.add_row ( "reds", "Mary Jane Watson", "mj (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-mj' );
				g.set_row_attr ( -1, 'changed', 'NO' );

				g.add_row ( "white", "Barry White", "barryw (@) sourceforge (dot) net" );
				g.set_row_attr ( -1, 'magic', 'magic-barryw' );
				g.set_row_attr ( -1, 'changed', 'NO' );

				// Enable sortable rows
				g.sortable = true;

				// Enable highlight of rows with the mouse
				g.highlight = true;

				g.set_col_editable ( 1, "txt" );
				g.set_col_editable ( 2, "txt" );

				g.sort_on_edit = true;

				// Show the grid replacing the original HTML object with the "grid" ID.
				g.render ();
			</script>
			<span onclick="collect_data(g)">Collect Data</span> - 
			<span onclick="post_form ( g, 'my_form' );">Post Form</span>
		</div>
	</div>
</div>

</body>
</html>

